﻿using CommunityToolkit.Mvvm.Messaging;
using HandyControl.Controls;
using HardToolApp.Model;
using HardToolApp.Tool;
using HardToolApp.View;
using NLua;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows;

namespace HardToolApp.ViewModel
{
    [ViewModelHelper("IIC主机", typeof(IICMasterPage), typeof(IICMasterModel), Sort = 3)]
    internal class IICMasterVM : CommVM
    {
        public IICMasterVM()
        {
            //ScriptVM.register("iic_master_set", "(clock,addrlen)", "IIC_Master", this.GetType(), "IIC主机设置", "0:操作成功,1:操作失败");
            ScriptVM.register("iic_master_send", "(发送数据:字符串 首个字节表示地址,超时时间)", "IIC_Master", this.GetType(), "IIC主机数据发送", "0:操作成功,1:操作失败");
            ScriptVM.register("iic_master_send_byte", "(发送数据:byte数组 首个字节表示地址,超时时间)", "IIC_Master", this.GetType(), "IIC主机数据发送", "0:操作成功,1:操作失败");
            ScriptVM.register("iic_master_read", "(地址,超时时间,读取长度)", "IIC_Master", this.GetType(), "IIC主机数据读取","读取的byte数组");
        }
        public override void ReadData()
        {
            Console.WriteLine("iic read data");
            if(((IICMasterModel)Model).readAddr %2 == 1)
            {
                Growl.Warning("地址错误，需要为偶数");
                return;
            }
            ((IICMasterModel)Model).subCmd = (byte)Communicate.SubCmd.ReadData;
            Send(((IICMasterModel)Model));
        }

        // 接收到串口相关
        public override void RecOkData(byte[] b)
        {
            if (b[4] == (byte)CommSubCmdIICMaster.COMM_SUB_IIC_MASTER_READ)//数据接收
            {
                string recString = Common.Byte2String(b.Skip(7).ToArray(), len: b[2] - 8);
                ((IICMasterModel)Model).receiveBytes = b[6].ToString("X2") + ':' + recString;
                USBInfoVM.USBVm.AddMap((b[3] << 8) + b[4], Common.String2Byte(recString));
            }
            else
            {
                USBInfoVM.USBVm.AddMap((b[3] << 8) + b[4], 0);
            }
        }
        #region IICMaster
        public static object iic_master_set(int clock,byte addrLen)
        {
            byte[] bytes = new byte[13];
            bytes[0] = 0x55;
            bytes[1] = 0xaa;
            bytes[2] = 13;
            bytes[3] = (byte)CommCmd.COMM_IIC_MASTER;
            bytes[4] = (byte)CommSubCmdIICMaster.COMM_SUB_IIC_MASTER_SET_PARAM;
            bytes[5] = (byte)((clock >> 24) & 0xff);
            bytes[6] = (byte)((clock >> 16) & 0xff);
            bytes[7] = (byte)((clock >> 8) & 0xff);
            bytes[8] = (byte)((clock >> 0) & 0xff);
            bytes[9] = (byte)(addrLen);
            bytes[10] = Common.chksum(bytes);
            return USBInfoVM.USBVm.send(bytes);
        }
        public static object iic_master_send(string sendBytes, UInt16 timeout)
        {
            byte[] data = Common.String2Byte(sendBytes);
            byte[] bytes = new byte[data.Count() + 8];
            bytes[0] = 0x55;
            bytes[1] = 0xaa;
            bytes[2] = (byte)(data.Count() + 8);
            bytes[3] = (byte)CommCmd.COMM_IIC_MASTER;
            bytes[4] = (byte)CommSubCmdIICMaster.COMM_SUB_IIC_MASTER_WRITE;
            bytes[5] = (byte)((timeout >> 8));
            bytes[6] = (byte)((timeout & 0xff));
            data.CopyTo(bytes, 7);
            bytes[data.Count() + 7] = Common.chksum(bytes);
            return USBInfoVM.USBVm.send(bytes, (int)timeout + 1000);
        }
        public static object iic_master_send_byte(LuaTable sendBytes, UInt16 timeout)
        {
            byte[] data = Common.Lua2Byte(sendBytes);
            byte[] bytes = new byte[data.Count() + 8];
            bytes[0] = 0x55;
            bytes[1] = 0xaa;
            bytes[2] = (byte)(data.Count() + 8);
            bytes[3] = (byte)CommCmd.COMM_IIC_MASTER;
            bytes[4] = (byte)CommSubCmdIICMaster.COMM_SUB_IIC_MASTER_WRITE;
            bytes[5] = (byte)((timeout >> 8));
            bytes[6] = (byte)((timeout & 0xff));
            data.CopyTo(bytes, 7);
            bytes[data.Count() + 7] = Common.chksum(bytes);
            return USBInfoVM.USBVm.send(bytes, (int)timeout + 1000);
        }

        public static object iic_master_read(byte addr,UInt16 timeout,byte readLen)
        {
            byte[] bytes = new byte[10];
            bytes[0] = 0x55;
            bytes[1] = 0xaa;
            bytes[2] = 10;
            bytes[3] = (byte)CommCmd.COMM_IIC_MASTER;
            bytes[4] = (byte)CommSubCmdIICMaster.COMM_SUB_IIC_MASTER_READ;
            bytes[5] = addr;
            bytes[6] = (byte)(timeout >> 8);
            bytes[7] = (byte)(timeout & 0xff);
            bytes[8] = (byte)readLen;
            bytes[9] = Common.chksum(bytes);
            return USBInfoVM.USBVm.send(bytes, (int)timeout + 1000);
        }
        /// <summary>
        /// 设置IIC参数
        /// </summary>
        /// <param name="m"></param>
        public override void Send(Peripheral peripheral)
        {
            IICMasterModel m = (IICMasterModel)peripheral;
            if (m.subCmd == (byte)Communicate.SubCmd.SetParam)
            {
                iic_master_set(m.clock,(byte)m.addrLen);
            }
            else if (m.subCmd == (byte)Communicate.SubCmd.SendData)
            {
                iic_master_send(m.sendBytes,m.timeout);
            }
            else if (m.subCmd == (byte)Communicate.SubCmd.ReadData)
            {
                iic_master_read(m.readAddr,m.timeout,(byte)m.readBytesLen);
            }
        }
        #endregion
    }
}
